package com.ztools.pc.service.impl.sys;

import cn.hutool.core.date.DateField;
import cn.hutool.core.date.DateTime;
import cn.hutool.core.date.DateUtil;
import cn.hutool.crypto.digest.DigestUtil;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.ztools.common.model.pc.sys.FileInfo;
import com.ztools.pc.mapper.sys.FileInfoMapper;
import com.ztools.pc.service.sys.FileInfoService;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.stereotype.Service;
import org.springframework.web.multipart.MultipartFile;

import java.io.File;
import java.io.IOException;
import java.util.ArrayList;
import java.util.Date;
import java.util.List;

/**
 * @Author:一口香菜
 * @Date: 2023/3/25  12:27
 * @Version 1.0
 */
@Slf4j
@Service
public class FileInfoServiceImpl extends ServiceImpl<FileInfoMapper, FileInfo> implements FileInfoService {

    @Value("${sys.file.uploadPath}")
    private String uploadPath;
    @Value("${sys.file.accessPath}")
    private String accessPath;

    /**
     * 文件上传
     *
     * @param files files
     * @return FileInfo
     */
    @Override
    public List<FileInfo> uploadFile(MultipartFile[] files) {
        log.info("uploading,file={}", files.length);
        List<FileInfo> resultList = new ArrayList<>();
        List<FileInfo> saveList = new ArrayList<>();
        try {
            for (MultipartFile file : files) {
                String fileMd5 = DigestUtil.md5Hex(file.getInputStream());
                String originalFileName = file.getOriginalFilename() == null ? "" : file.getOriginalFilename();
                String fileName = fileMd5 + originalFileName.substring(originalFileName.lastIndexOf("."));
                FileInfo fileInfo = FileInfo.builder()
                        .fileName(fileName)
                        .fileSize(file.getSize())
                        .fileType(file.getContentType())
                        .fileMd5(fileMd5)
                        .uploadDate(new Date())
                        .build();
                fileInfo.setFileLocation(getFileLocation(fileInfo.getUploadDate()) + fileName);
                fileInfo.setFileUrl(getAccessLocation(fileInfo.getUploadDate()) + fileName);
                // 查询该文件是存在数据库
                QueryWrapper<FileInfo> queryWrapper = new QueryWrapper<>();
                queryWrapper.eq("file_md5", fileMd5);
                FileInfo fileByMd5 = getOne(queryWrapper);
                if (fileByMd5 == null) {
                    saveList.add(fileInfo);
                    resultList.add(fileInfo);
                    File toSave = new File(getFileLocation(fileInfo.getUploadDate()));
                    if (!toSave.exists()) {
                        log.info("mkdirs");
                        boolean isDirs = toSave.mkdirs();
                    }
                    file.transferTo(new File(fileInfo.getFileLocation()).getAbsoluteFile());
                } else {
                    resultList.add(fileInfo);
                }
            }
        } catch (IOException e) {
            e.printStackTrace();
        }
        if (saveList.size() > 0) {
            saveBatch(saveList);
        }
        log.info("图片上传成功:saveList:{},resultList:{}", saveList.size(), resultList.size());
        return resultList;
    }

    /**
     * 文件保存地址
     *
     * @param date date
     * @return
     */
    public String getFileLocation(Date date) {
        DateTime dateTime = DateUtil.date(date);
        int year = dateTime.getField(DateField.YEAR);
        int month = dateTime.getField(DateField.MONTH) + 1;
        int day = dateTime.getField(DateField.DAY_OF_MONTH);
        return uploadPath + year + File.separator + month + File.separator + day + File.separator;
    }

    /**
     * 文件访问地址
     *
     * @param date date
     * @return
     */
    public String getAccessLocation(Date date) {
        DateTime dateTime = DateUtil.date(date);
        int year = dateTime.getField(DateField.YEAR);
        int month = dateTime.getField(DateField.MONTH) + 1;
        int day = dateTime.getField(DateField.DAY_OF_MONTH);
        return accessPath + year + File.separator + month + File.separator + day + File.separator;

    }


}
